package com.fundynamic.bowlingkata;

public class Game {

	private static final int MAXIMUM_ROLLS_IN_GAME = 21;
	private static final int MAXIMUM_FRAMES_IN_GAME = 10;
	
	private int rolls[] = new int[MAXIMUM_ROLLS_IN_GAME];
	private int currentRoll = 0;
	
	public void roll(int pins) {
		rolls[currentRoll] = pins;
		currentRoll++;
	}

	public int score() {
		int score = 0;
		int frameIndex = 0;
		
		for (int frame = 0; frame < MAXIMUM_FRAMES_IN_GAME; frame++) {
			int frameScore = 0;
			
			if (isSpare(frameIndex)) {
				frameScore = 10 + spareBonus(frameIndex);
				frameIndex += 2;
			} else if (isStrike(frameIndex)) {
				frameScore += 10 + strikeBonus(frameIndex);
				frameIndex++;
			} else {
				frameScore = normalScoreForFrame(frameIndex, frameScore);
				frameIndex += 2;
			}
			score += frameScore;
		}
		
		return score;
	}

	private int normalScoreForFrame(int frameIndex, int frameScore) {
		frameScore += rolls[frameIndex];
		frameScore += rolls[frameIndex + 1];
		return frameScore;
	}

	private int strikeBonus(int frameIndex) {
		return rolls[frameIndex + 1] + rolls[frameIndex + 2];
	}

	private boolean isStrike(int frameIndex) {
		return rolls[frameIndex] == 10;
	}

	private int spareBonus(int frameIndex) {
		return rolls[frameIndex + 2];
	}

	private boolean isSpare(int frameIndex) {
		return (rolls[frameIndex] + rolls[frameIndex + 1]) == 10;
	}

}
